# encoding: utf-8
from enum import Enum
from dataclasses import dataclass
from concurrent.futures import ThreadPoolExecutor, TimeoutError as FuturesTimeoutError
from typing import Any, Callable, Optional

class Exchange(Enum):
    """交易所枚举"""
    SHFE = "上海期货交易所"
    DCE = "大连商品交易所"
    CZCE = "郑州商品交易所"
    CFFEX = "中国金融期货交易所"
    INE = "上海国际能源交易中心"


@dataclass
class ContractDateInfo:
    """合约信息"""
    contract_code: str  # 合约代码
    month: str         # 月份
    listing_date: str  # 上市日
    last_trading_date: str  # 最后交易日


def run_with_timeout(
    func: Callable[..., Any],
    timeout: Optional[float] = None,
    *args: Any,
    **kwargs: Any,
) -> Any:
    """运行可调用对象并在超时时间内等待结果。

    注意：底层阻塞调用（例如第三方库的网络请求）在超时后不会被强制中断，
    但本函数会返回超时错误，调用方可选择忽略迟到结果。

    Args:
        func: 需要执行的函数
        timeout: 超时时间（秒），为 None 时不限制
        *args, **kwargs: 透传给函数的参数

    Returns:
        函数返回值；若超时则抛出 TimeoutError
    """
    with ThreadPoolExecutor(max_workers=1) as executor:
        future = executor.submit(func, *args, **kwargs)
        try:
            return future.result(timeout=timeout)
        except FuturesTimeoutError as e:
            raise TimeoutError(f"Operation timed out after {timeout} seconds") from e
